/**
 * @file    deye_rs485.c
 * @brief   逆变器协议-德业-RS485协议
 * @author  Liuwei
 * @version 1.0.1
 * @date    2023-07-10
 * 
 * @copyright Copyright (c) 2023 JBD-Energy Storage Technology Co. LTD
 * 
 * @par 修改日志:
 * <table>
 * <tr><th>Date       <th>Version   <th>Author   <th>Description
 * <tr><td>2023-07-10 <td>1.0.1     <td>Liuwei   <td>首次创建
 * </table>
 */

/* includes ------------------------------------------------------------------*/
#include "deye_rs485.h"
#include "modbus_app.h"
#include "if_di.h"
#include "cfg_prj.h"
#include "sample.h"
#include "parallel_com.h"
#include "var_mng.h"
#include "param_mng.h"
/* macro/define --------------------------------------------------------------*/

/* typedef -------------------------------------------------------------------*/
#define INTPUT_REG_SIZE      (0x20)
#define IN_REG_START_ADDR    (0x1000)
#define CMD_READ_IN_REG      (0x04)
#define CMD_READ_INFO        (0x11)
/* local functions -----------------------------------------------------------*/
static uint8_t deye_read_input_reg(md_data_type md_data_msg , uint8_t *tx_buf ,uint16_t *tx_len);
static uint8_t deye_update_input_buf(void);
static uint8_t deye_read_info_reg(md_data_type md_data_msg , uint8_t *tx_buf ,uint16_t *tx_len);
static uint16_t get_prp_msg(void);
/* static variables ----------------------------------------------------------*/
static uint16_t input_reg_buf[INTPUT_REG_SIZE] = {0};

/* global variables ----------------------------------------------------------*/

/** ------------------------------------------------------------------------- *
  *                             Global function
 ** ------------------------------------------------------------------------- */
uint8_t deye_rs485_analysis(uint8_t *rx_buf , uint16_t rx_len ,uint8_t *tx_buf , uint16_t *tx_len)
{
    md_data_type recv_md_data = {0};
    if(TRUE == modbus_rtu_analysis(rx_buf , rx_len , &recv_md_data))
    {
        if(1 == recv_md_data.addr)
        {
            if((recv_md_data.reg_addr + recv_md_data.data_len >= IN_REG_START_ADDR)
			  &&(recv_md_data.reg_addr + recv_md_data.data_len <= (IN_REG_START_ADDR + INTPUT_REG_SIZE))
              &&(CMD_READ_IN_REG == recv_md_data.cmd_code))
            {
				recv_md_data.reg_addr -= IN_REG_START_ADDR;
                deye_update_input_buf();
                return deye_read_input_reg(recv_md_data , tx_buf , tx_len);
            }
            else if(CMD_READ_INFO == recv_md_data.cmd_code)
            {
                return deye_read_info_reg(recv_md_data , tx_buf , tx_len);
            }
            return FALSE;
        }
        return FALSE;
    }
    return FALSE;
}

/** ------------------------------------------------------------------------- *
  *                              Local function
 ** ------------------------------------------------------------------------- */
static uint8_t deye_read_input_reg(md_data_type md_data_msg , uint8_t *tx_buf ,uint16_t *tx_len)
{
    uint16_t data_len = 0;
    uint16_t crc_code = 0;
    uint8_t i = 0;
    uint8_t *p_tx = tx_buf;

    *p_tx ++ = md_data_msg.addr;
    *p_tx ++ = md_data_msg.cmd_code;
    *p_tx ++ = md_data_msg.data_len * 2; 
    data_len = md_data_msg.data_len * 2;
    for(i = 0;i < md_data_msg.data_len; ++ i)
    {
        *p_tx ++ = input_reg_buf[i + md_data_msg.reg_addr] >> 8;
        *p_tx ++  = input_reg_buf[i + md_data_msg.reg_addr] & 0xff;
    }

    crc_code = modbus_calc_crc(tx_buf , data_len + 3);

    *p_tx ++ = crc_code;
    *p_tx ++ = crc_code >> 8;

    *tx_len = (data_len + 5);
	
	return TRUE;
} 

static uint8_t deye_update_input_buf(void)
{
	uint16_t soh = 0;
	uint32_t cap_val = 0;
    input_reg_buf[0x00] = var_get_data(VAR_ID_TP_VOLT);
	input_reg_buf[0x01] = master_data_reg.total_bus_curr ;//实测符合
	cap_val = master_data_reg.total_real_cap;
	if(cap_val >= MAX_DISP_CAP)
		cap_val = MAX_DISP_CAP;
    input_reg_buf[0x02] = cap_val;  // 不用总的数据位不够会溢出 
    input_reg_buf[0x03] = var_get_data(VAR_ID_TP_AVG_TEMP) - 2731;
	input_reg_buf[0x04] = var_get_data(VAR_ID_ENV_TEMP) - 500; //增加平均
    input_reg_buf[0x05] = 0;
    input_reg_buf[0x06] = get_prp_msg();
	input_reg_buf[0x07] = 0;
    input_reg_buf[0x08] = var_get_data(VAR_ID_TP_SOC) * 10;
	soh = var_get_data(VAR_ID_TP_SOH);
	if(soh > 100)
		soh = 100;
    input_reg_buf[0x09] = soh * 10;
	
	cap_val = master_data_reg.total_full_cap;
	if(cap_val >= MAX_DISP_CAP)
		cap_val = MAX_DISP_CAP;
    input_reg_buf[0x0A] = cap_val; 
	input_reg_buf[0x0B] = var_get_data(VAR_ID_TP_CYCLE);
    input_reg_buf[0x0C] = var_get_data(VAR_ID_TP_SOP_CC) * 10;
    input_reg_buf[0x0D] = var_get_data(VAR_ID_TP_MAXC_VOLT);
	input_reg_buf[0x0E] = var_get_data(VAR_ID_TP_MINC_VOLT);
    input_reg_buf[0x0F] = 0xFFFF;
    input_reg_buf[0x10] = var_get_data(VAR_ID_TP_MAXT_VAL)-2731;
    input_reg_buf[0x11] = var_get_data(VAR_ID_TP_MINT_VAL)-2731;
	input_reg_buf[0x12] = var_get_data(VAR_ID_MOS_TEMP) - 500; //增加平均
    input_reg_buf[0x13] = 0;
    input_reg_buf[0x14] = var_get_data(VAR_ID_TP_SOP_CV) * 10;
	input_reg_buf[0x15] = var_get_data(VAR_ID_TP_FULL_CAP); //
    input_reg_buf[0x16] = 0;

	return TRUE;
}

static uint8_t deye_read_info_reg(md_data_type md_data_msg , uint8_t *tx_buf ,uint16_t *tx_len)
{
    uint16_t data_len = 0;
    uint16_t crc_code = 0;
    uint8_t i = 0;
	uint16_t data_temp = 0;
	
    uint8_t *p_tx = tx_buf;

    *p_tx ++ = md_data_msg.addr;
    *p_tx ++ = md_data_msg.cmd_code;
    *p_tx ++ = 43;
    data_len = 43;
    for(i = 0;i < 7; ++ i)
    {
        data_temp = param_get_data(PAR_ID_BMS_CODE + i);
        *p_tx ++ = data_temp >> 8;
		*p_tx ++ = data_temp & 0xff;
    }
	data_temp = param_get_data(PAR_ID_BMS_CODE + i);
	*p_tx ++ = data_temp >> 8;
	*p_tx ++ = '*';
	*p_tx ++ = SOFT_VER_MAIN;
	*p_tx ++ = SOFT_VER_RELEASE;
	*p_tx ++ = '*';
	*p_tx ++ = 0;
	*p_tx ++ = var_get_data(VAR_ID_HARD_VER);
	*p_tx ++ = '*';
	for(i = 0;i < 10; ++ i)
    {
        data_temp = param_get_data(PAR_ID_SN_CODE + i);
        *p_tx ++ = data_temp >> 8;
		*p_tx ++ = data_temp & 0xff;
    }
	*p_tx ++ = '*';
	
    crc_code = modbus_calc_crc(tx_buf , data_len + 3);

    *p_tx ++ = crc_code;
    *p_tx ++ = crc_code >> 8;

    *tx_len = (data_len + 5);
	
	return TRUE;
}

static uint16_t get_prp_msg(void)
{
	uint16_t prp_msg = 0;
	
	if(master_data_reg.total_prp_msg.bit.sc)
		prp_msg |= (1 << 4);
	if(master_data_reg.total_prp_msg.bit.occ || master_data_reg.total_prp_msg.bit.ocd)
		prp_msg |= (1 << 5);
	if(master_data_reg.total_prp_msg.bit.otc)
		prp_msg |= (1 << 6);
	if(master_data_reg.total_prp_msg.bit.utc)
		prp_msg |= (1 << 7);
	if(master_data_reg.total_prp_msg.bit.otd)
		prp_msg |= (1 << 8);
	if(master_data_reg.total_prp_msg.bit.utd)
		prp_msg |= (1 << 9);

	return prp_msg;
}
/********** Copyright (c) 2023 JBD-Energy Storage Technology Co. LTD *********/
